<?php

namespace App\Jobs\Mp;

use App\Jobs\TempleteMessageJob;
use App\Lib\WeApp\WeApp;
use App\Models\Mp\WxMpFreePublish;
use App\Models\User\WxUser;
use App\Models\User\WxUserOnline;
use App\Wen\Utils\Settings;
use App\Wen\Utils\StrUtils;
use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldBeUnique;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Queue\SerializesModels;
use Illuminate\Support\Carbon;

class FreePublishSubmitJob implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
    protected $free_publish_id;
    protected $tenant_id;
    protected $posts_id;
    public $tries = 1;
    public $max_try = 0;
    /**
     * Create a new job instance.
     *
     * @return void
     */
    public function __construct($free_publish_id, $tenant_id, $posts_id, $max_try)
    {
        $this->free_publish_id = $free_publish_id;
        $this->tenant_id = $tenant_id;
        $this->posts_id = $posts_id;
        $this->max_try = $max_try;
    }

    /**
     * Execute the job.
     *
     * @return void
     */
    public function handle()
    {
        if(_empty_($this->free_publish_id)){
            return;
        }
        if(_empty_($this->tenant_id)){
            $from_tenant = get_object_meta('mp_free_publish', $this->free_publish_id, 'from_tenant', 'n');
            if($from_tenant && $from_tenant > 0){
                $this->tenant_id = $from_tenant;
            }
        }

        $free_publish = WxMpFreePublish::find($this->free_publish_id);
        if(!$free_publish){
            return;
        }

        $weapp = new WeApp('mp');
        $mp = $weapp->getMpServicer();

        if($free_publish->parent_id > 0) {
            return;
        }

        if($this->max_try <= 0){
            return;
        }
        $this->max_try = $this->max_try - 1;

        if (_empty_($free_publish->publish_id)) {
            $res = $mp->freePublishSubmit($free_publish->id);
        } else{
            if (in_array($free_publish->publish_status, [2, 3, 4, 5, 6])) {
                $res = $mp->freePublishSubmit($free_publish->id);
            } else if ($free_publish->publish_status == 1) {
                PublishGetStatusJob::dispatch($free_publish->publish_id);
                FreePublishSubmitJob::dispatch($this->free_publish_id, $this->tenant_id, $this->posts_id, $this->max_try)->delay(now()->addMinutes(4));
                return;
            } else{
                $res = [
                    'code' => 200
                ];
            }
        }
        if($res['code'] == 200){
            // 发布成功
            $free_publish = WxMpFreePublish::find($this->free_publish_id);
            if(!$free_publish){
                return;
            }
            if(_empty_($free_publish->article_url)){
                if(!_empty_($free_publish->publish_id)){
                    PublishGetStatusJob::dispatch($free_publish->publish_id);
                    FreePublishSubmitJob::dispatch($this->free_publish_id, $this->tenant_id, $this->posts_id, $this->max_try)->delay(now()->addMinutes(4));
                    return;
                }else{
                    return;
                }
            }

            $user_range = Settings::get('app_mp_free_publish_user_range', 3);
            $tenant_alone = Settings::get('app_mp_free_publish_tenant_alone', 2);
            $tenDaysAgo = Carbon::now()->subDays(10 * $user_range);
            $publish_duration_second = Settings::get('app_mp_free_publish_duration', 2) * 60 * 60;

            foreach ($this->posts_id as $tmp_post_id){
                if($this->tenant_id > 0 || ($this->tenant_id === 0 && $tenant_alone == 2)){
                    update_post_meta($tmp_post_id, 'mp_free_publish_'.$this->tenant_id, 1, 's');
                }else{
                    update_post_meta($tmp_post_id, 'mp_free_publish_all', 1, 's');
                }
            }

            // 查询最近 10 天内在线过的用户 ID
            if($this->tenant_id > 0 || ($this->tenant_id === 0 && $tenant_alone == 2)){
                $userIds = WxUserOnline::join('wx_user', 'wx_user_online.user_id', '=', 'wx_user.id')
                    ->whereNotNull('wx_user.weixin_mp_openid')
                    ->where('wx_user.tenant_id', $this->tenant_id)
                    ->where('wx_user_online.online', '>=', $tenDaysAgo)
                    ->pluck('wx_user_online.user_id')
                    ->toArray();
            }else{
                $userIds = WxUserOnline::join('wx_user', 'wx_user_online.user_id', '=', 'wx_user.id')
                    ->whereNotNull('wx_user.weixin_mp_openid')
                    ->where('wx_user_online.online', '>=', $tenDaysAgo)
                    ->pluck('wx_user_online.user_id')
                    ->toArray();
            }

            if($userIds){
                $templateId = Settings::get('template_message_notice_id');
                if(_empty_($templateId)){
                    return null;
                }

                $title = '已订阅推文（回退订取消）';
                $per_second = _between_((int)($publish_duration_second / count($userIds)), 1, 1000);
                $key1 = strip_tags($free_publish->title ?? '');
                $key2 = '';
                $key3 = '';
                $app_id = Settings::get('app_id');
                for ($i = 0; $i < count($userIds); $i++){
                    $uid = $userIds[$i];
                    if(get_user_meta($uid, 'is_mp_free_publish_notice','n') == 2){
                        continue;
                    }

                    $userOpenID = WxUser::where('id', $uid)->where('user_state', 0)->value('weixin_mp_openid');
                    if(_empty_($userOpenID)){
                        continue;
                    }

                    $data=array(
                        'first'=>array('value'=>$title,'color'=>"#FF0000"),
                        'keyword1'=>array('value'=>$key1,'color'=>'#999999'),
                        'keyword2'=>array('value'=>$key2,'color'=>'#FF0000'),
                        'keyword3'=>array('value'=>$key3,'color'=>'#FF0000'),
                        'remark' =>array('value'=>'','color'=>'#999999'),
                        'time33' => [
                            'value' => date('Y年m月d日 H:i', time()),
                        ],
                        'thing19' => [
                            'value' => $title,
                        ],
                        'thing6' => [
                            'value' => StrUtils::limit($key1),
                        ]
                    );

                    TempleteMessageJob::dispatch([
                        'touser' => $userOpenID,
                        'template_id' => $templateId,
                        'url' => $free_publish->article_url,
                        'data' => $data,
                    ])->delay(now()->addSeconds($per_second * $i));
                }
            }
        }else{
            _logger_(__file__, __line__, $free_publish->id.'自动发布失败: '.$res['msg']);
        }

    }
}
